using System.Collections.Generic;
using UnityEngine;

/// <summary>
/// 高级Boid控制器 - 无刚体版本，支持跟随多种目标（包括玩家）
/// </summary>
public class Boid : MonoBehaviour
{
    // ========== 运动参数 ==========
    [Header("基本运动参数")]
    [Tooltip("最小移动速度"), Range(0.1f, 10f)]
    public float minSpeed = 2f;
    [Tooltip("最大移动速度"), Range(0.1f, 20f)]
    public float maxSpeed = 5f;
    [Tooltip("转向速度"), Range(0.1f, 10f)]
    public float rotationSpeed = 5f;
    [Tooltip("邻居检测半径"), Range(0.1f, 20f)]
    public float neighborRadius = 3f;

    // ========== 行为权重 ==========
    [Header("行为权重系数")]
    [Tooltip("分离行为权重"), Range(0f, 5f)]
    public float separationWeight = 1f;
    [Tooltip("对齐行为权重"), Range(0f, 5f)]
    public float alignmentWeight = 1f;
    [Tooltip("聚集行为权重"), Range(0f, 5f)]
    public float cohesionWeight = 1f;
    [Tooltip("目标跟随权重"), Range(0f, 10f)]
    public float targetWeight = 2f;
    [Tooltip("环绕行为权重"), Range(0f, 5f)]
    public float orbitWeight = 1f;
    [Tooltip("随机力权重"), Range(0f, 2f)]
    public float randomForceWeight = 0.5f;
    [Tooltip("随机方向更新间隔（秒）"), Range(0.1f, 5f)]
    public float randomUpdateInterval = 1f;

    // ========== 运行时变量 ==========
    private Transform currentTarget;       // 当前跟随目标
    private float currentOrbitRadius;     // 当前环绕半径
    private float currentOrbitSpeed;      // 当前环绕速度
    private float currentMaxDistance;     // 最大允许距离
    private Vector3 velocity;             // 当前速度
    private Vector3 randomDirection;      // 随机力方向
    private float lastRandomUpdateTime;   // 上次随机更新时间
    private List<Boid> neighbors = new List<Boid>(); // 邻居列表

    // ========== 目标类型 ==========
    public enum TargetType
    {
        SpawnPoint,  // 普通生成点
        Player       // 玩家
    }
    private TargetType currentTargetType; // 当前目标类型

    /// <summary>
    /// 初始化方法 - 由SpawnPoint或Player调用
    /// </summary>
    public void Initialize(Transform target, float orbitRadius, float orbitSpeed,
                         float targetWeight, float maxDistance, TargetType targetType,
                         Vector3 initialVelocity = default)
    {
        // 设置初始参数
        currentTarget = target;
        currentOrbitRadius = orbitRadius;
        currentOrbitSpeed = orbitSpeed;
        this.targetWeight = targetWeight;
        currentMaxDistance = maxDistance;
        currentTargetType = targetType;

        // 设置初始速度（随机方向，速度在最小和最大之间）
        // velocity = Random.insideUnitSphere * Random.Range(minSpeed, maxSpeed) * 0.1f;
        velocity = initialVelocity != default ? initialVelocity :
          Random.insideUnitSphere * Random.Range(minSpeed, maxSpeed) * 0.1f;

        // 根据目标类型调整行为
        if (targetType == TargetType.Player)
        {
            // 玩家跟随的鸟可以有不同表现
            minSpeed *= 1.2f;
            maxSpeed *= 1.2f;
            this.targetWeight *= 1.5f;
        }
    }

    void Update()
    {
        if (currentTarget == null) return;

        UpdateBehavior(); // 更新行为逻辑
        MoveBoid();       // 应用移动
    }

    /// <summary>
    /// 更新所有行为逻辑
    /// </summary>
    private void UpdateBehavior()
    {
        FindNeighbors(); // 检测邻居

        // 计算各种行为力
        Vector3 separation = CalculateSeparation() * separationWeight;
        Vector3 alignment = CalculateAlignment() * alignmentWeight;
        Vector3 cohesion = CalculateCohesion() * cohesionWeight;
        Vector3 targetForce = CalculateTargetForce() * targetWeight;
        Vector3 orbitForce = CalculateOrbitForce() * orbitWeight;
        Vector3 randomForce = CalculateRandomForce() * randomForceWeight;

        // 合并所有力（使用加权平均）
        Vector3 combinedForce = (separation + alignment + cohesion + targetForce + orbitForce + randomForce) / 6f;

        // 应用力到速度（使用时间平滑）
        velocity = Vector3.Lerp(velocity, velocity + combinedForce, Time.deltaTime);

        // 限制速度范围
        LimitSpeed();
    }

    /// <summary>
    /// 应用移动
    /// </summary>
    private void MoveBoid()
    {
        // 直接修改位置（无物理）
        transform.position += velocity * Time.deltaTime;

        // 平滑旋转朝向移动方向
        if (velocity != Vector3.zero)
        {
            Quaternion targetRotation = Quaternion.LookRotation(velocity);
            transform.rotation = Quaternion.Slerp(
                transform.rotation,
                targetRotation,
                rotationSpeed * Time.deltaTime
            );
        }
    }

    /// <summary>
    /// 检测周围邻居
    /// </summary>
    private void FindNeighbors()
    {
        neighbors.Clear();

        // 简单的球形检测（可优化为空间分区）
        Collider[] nearbyColliders = Physics.OverlapSphere(
            transform.position,
            neighborRadius
        );

        foreach (Collider col in nearbyColliders)
        {
            Boid otherBoid = col.GetComponent<Boid>();
            // 确保不是自己，且是有效的Boid
            if (otherBoid != null && otherBoid != this)
            {
                neighbors.Add(otherBoid);
            }
        }
    }

    /// <summary>
    /// 计算目标吸引力（距离越远力量越大）
    /// </summary>
    private Vector3 CalculateTargetForce()
    {
        Vector3 toTarget = currentTarget.position - transform.position;
        float distance = toTarget.magnitude;

        // 非线性吸引力：距离越远力量越大（使用平方关系）
        float attractionFactor = Mathf.Pow(distance / currentOrbitRadius, 2f);

        return toTarget.normalized * attractionFactor;
    }

    /// <summary>
    /// 计算环绕力（向心力+切向力）
    /// </summary>
    private Vector3 CalculateOrbitForce()
    {
        Vector3 toTarget = currentTarget.position - transform.position;
        float distance = toTarget.magnitude;

        // 向心力（指向目标，强度随距离增加）
        Vector3 centripetal = toTarget.normalized *
            (distance / currentOrbitRadius) * currentOrbitSpeed;

        // 切向力（环绕目标）
        Vector3 tangent = Vector3.Cross(toTarget, Vector3.up).normalized *
            currentOrbitSpeed;

        // 混合两种力（0.5的比例可以调整）
        return (centripetal + tangent) * 0.5f;
    }

    /// <summary>
    /// 限制速度在合理范围内
    /// </summary>
    private void LimitSpeed()
    {
        float currentSpeed = velocity.magnitude;

        if (currentSpeed > maxSpeed)
        {
            velocity = velocity.normalized * maxSpeed;
        }
        else if (currentSpeed < minSpeed)
        {
            velocity = velocity.normalized * minSpeed;
        }
    }

    /// <summary>
    /// 计算分离力（避免与邻居碰撞）
    /// </summary>
    private Vector3 CalculateSeparation()
    {
        Vector3 separation = Vector3.zero;

        foreach (Boid neighbor in neighbors)
        {
            Vector3 awayVector = transform.position - neighbor.transform.position;
            // 距离越近排斥力越大（使用平方反比）
            separation += awayVector.normalized / Mathf.Max(awayVector.sqrMagnitude, 0.1f);
        }

        return separation;
    }

    /// <summary>
    /// 计算对齐力（与邻居平均方向一致）
    /// </summary>
    private Vector3 CalculateAlignment()
    {
        if (neighbors.Count == 0) return Vector3.zero;

        Vector3 avgVelocity = Vector3.zero;
        foreach (Boid neighbor in neighbors)
        {
            avgVelocity += neighbor.velocity;
        }
        avgVelocity /= neighbors.Count;

        return (avgVelocity - velocity).normalized;
    }

    /// <summary>
    /// 计算聚合力（向邻居中心靠拢）
    /// </summary>
    private Vector3 CalculateCohesion()
    {
        if (neighbors.Count == 0) return Vector3.zero;

        Vector3 avgPosition = Vector3.zero;
        foreach (Boid neighbor in neighbors)
        {
            avgPosition += neighbor.transform.position;
        }
        avgPosition /= neighbors.Count;

        return (avgPosition - transform.position).normalized;
    }
    /// <summary>
    /// 计算随机力（定期更新随机方向）
    /// </summary>
    private Vector3 CalculateRandomForce()
    {
        // 定期更新随机方向
        if (Time.time - lastRandomUpdateTime > randomUpdateInterval)
        {
            randomDirection = Random.insideUnitSphere;
            lastRandomUpdateTime = Time.time;
        }
        return randomDirection;
    }

    /// <summary>
    /// 检查距离有效性（是否超出最大范围）
    /// </summary>
    public bool CheckDistanceAndValidity()
    {
        if (currentTarget == null) return true;

        float distance = Vector3.Distance(transform.position, currentTarget.position);
        return distance > currentMaxDistance;
    }

    /// <summary>
    /// 切换跟随目标（用于玩家捕获鸟群）
    /// </summary>
    public void FollowNewTarget(Transform newTarget, TargetType newTargetType)
    {
        currentTarget = newTarget;
        currentTargetType = newTargetType;

        // 根据新目标类型调整参数
        if (newTargetType == TargetType.Player)
        {
            // 跟随玩家时增加速度和响应性
            minSpeed *= 1.5f;
            maxSpeed *= 1.5f;
            targetWeight *= 2f;
            orbitWeight *= 0.8f; // 减少环绕力，更倾向于直接跟随
        }
    }

    /// <summary>
    /// 在编辑器中可视化检测范围和关系
    /// </summary>
    private void OnDrawGizmosSelected()
    {
        // 绘制邻居检测范围
        Gizmos.color = new Color(0, 1, 1, 0.3f);
        Gizmos.DrawWireSphere(transform.position, neighborRadius);

        // 绘制与目标的连线
        if (currentTarget != null)
        {
            Gizmos.color = Color.yellow;
            Gizmos.DrawLine(transform.position, currentTarget.position);

            // 绘制目标环绕半径
            Gizmos.color = new Color(1, 1, 0, 0.2f);
            Gizmos.DrawWireSphere(currentTarget.position, currentOrbitRadius);
        }

        // 绘制当前速度方向
        Gizmos.color = Color.green;
        Gizmos.DrawRay(transform.position, velocity.normalized * 2f);
    }
}